chore: update MUI to v7#1347
Conversation
Signed-off-by: Rajesh-Nagarajan-11 <rajeshnagarajan36@gmail.com>
|
@Rajesh-Nagarajan-11 Ci failing. Test first with meshery-ui with local references |
|
I tested with meshery ui it's works good , let me check again 👀 |
Signed-off-by: Rajesh-Nagarajan-11 <rajeshnagarajan36@gmail.com>
Signed-off-by: Rajesh-Nagarajan-11 <rajeshnagarajan36@gmail.com>
There was a problem hiding this comment.
Pull request overview
Updates this component library’s MUI integration and packaging/build config to support MUI v7 and improved ESM/CJS consumption.
Changes:
- Bump
@mui/material/@mui/icons-materialto v7 and adjust a few MUI imports to updated entry points. - Update build output metadata (
module,exports) and tsup externals handling to avoid bundling MUI/emotion. - Replace the removed MUI
Hiddencomponent wrapper with a custom breakpoint-based implementation and adjustGrid2imports/wrappers.
Reviewed changes
Copilot reviewed 12 out of 13 changed files in this pull request and generated 7 comments.
Show a summary per file
| File | Description |
|---|---|
| tsup.config.ts | Computes external from dependencies/peerDependencies (plus MUI/emotion regex) to avoid rebundling. |
| src/theme/typography.ts | Updates MUI typography type import/return type for theme typography configuration. |
| src/custom/Workspaces/WorkspaceCard.tsx | Switches Grid2 import style as part of MUI v7 migration. |
| src/custom/TransferModal/TransferList/style.tsx | Switches Grid2 import style inside styled components. |
| src/custom/TeamTable/TeamTable.tsx | Switches Grid2 import style as part of MUI v7 migration. |
| src/custom/Stepper/index.tsx | Moves styled import to @mui/material/styles. |
| src/custom/ResourceDetailFormatters/styles.ts | Switches Grid2 import style inside styled components. |
| src/custom/InputSearchField/InputSearchField.tsx | Switches Grid2 import style as part of MUI v7 migration. |
| src/custom/DashboardWidgets/GettingStartedWidget/GetStartedModal.tsx | Switches Grid2 import style as part of MUI v7 migration. |
| src/base/Hidden/Hidden.tsx | Replaces MUI Hidden with a custom useMediaQuery implementation. |
| src/base/Grid2/Grid2.tsx | Alters the Grid2 wrapper implementation. |
| package.json | Updates MUI versions; adds exports; points module to ESM output. |
| package-lock.json | Locks updated MUI v7 (and related) transitive dependencies. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| mdDown?: boolean; | ||
| lgDown?: boolean; | ||
| xlDown?: boolean; | ||
| implementation?: 'js' | 'css'; |
There was a problem hiding this comment.
HiddenProps exposes an implementation prop, but the component ignores it entirely. This is misleading API surface and can break callers expecting CSS-based hiding behavior. Either implement the implementation option or remove it from the public props type to avoid false expectations.
| implementation?: 'js' | 'css'; |
| const xsOnly = useMediaQuery(theme.breakpoints.only('xs')); | ||
| const smOnly = useMediaQuery(theme.breakpoints.only('sm')); | ||
| const mdOnly = useMediaQuery(theme.breakpoints.only('md')); | ||
| const lgOnly = useMediaQuery(theme.breakpoints.only('lg')); | ||
| const xlOnly = useMediaQuery(theme.breakpoints.only('xl')); | ||
|
|
||
| const xsUpMatch = useMediaQuery(theme.breakpoints.up('xs')); | ||
| const smUpMatch = useMediaQuery(theme.breakpoints.up('sm')); | ||
| const mdUpMatch = useMediaQuery(theme.breakpoints.up('md')); | ||
| const lgUpMatch = useMediaQuery(theme.breakpoints.up('lg')); | ||
| const xlUpMatch = useMediaQuery(theme.breakpoints.up('xl')); | ||
|
|
||
| const xsDownMatch = useMediaQuery(theme.breakpoints.down('xs')); | ||
| const smDownMatch = useMediaQuery(theme.breakpoints.down('sm')); | ||
| const mdDownMatch = useMediaQuery(theme.breakpoints.down('md')); | ||
| const lgDownMatch = useMediaQuery(theme.breakpoints.down('lg')); | ||
| const xlDownMatch = useMediaQuery(theme.breakpoints.down('xl')); | ||
|
|
||
| const onlyMatches = | ||
| (onlyValues.includes('xs') && xsOnly) || | ||
| (onlyValues.includes('sm') && smOnly) || | ||
| (onlyValues.includes('md') && mdOnly) || | ||
| (onlyValues.includes('lg') && lgOnly) || | ||
| (onlyValues.includes('xl') && xlOnly); | ||
|
|
||
| const upMatches = | ||
| (xsUp && xsUpMatch) || | ||
| (smUp && smUpMatch) || | ||
| (mdUp && mdUpMatch) || | ||
| (lgUp && lgUpMatch) || | ||
| (xlUp && xlUpMatch); | ||
|
|
||
| const downMatches = | ||
| (xsDown && xsDownMatch) || | ||
| (smDown && smDownMatch) || | ||
| (mdDown && mdDownMatch) || | ||
| (lgDown && lgDownMatch) || | ||
| (xlDown && xlDownMatch); | ||
|
|
||
| if (onlyMatches || upMatches || downMatches) { |
There was a problem hiding this comment.
Hidden runs useMediaQuery for every breakpoint (only/up/down) on every render, even when the corresponding props aren’t provided. This is avoidable work and can add up if Hidden is used widely. Consider computing only the queries needed based on only, *Up, and *Down props (or deriving a single combined media query).
| const xsOnly = useMediaQuery(theme.breakpoints.only('xs')); | |
| const smOnly = useMediaQuery(theme.breakpoints.only('sm')); | |
| const mdOnly = useMediaQuery(theme.breakpoints.only('md')); | |
| const lgOnly = useMediaQuery(theme.breakpoints.only('lg')); | |
| const xlOnly = useMediaQuery(theme.breakpoints.only('xl')); | |
| const xsUpMatch = useMediaQuery(theme.breakpoints.up('xs')); | |
| const smUpMatch = useMediaQuery(theme.breakpoints.up('sm')); | |
| const mdUpMatch = useMediaQuery(theme.breakpoints.up('md')); | |
| const lgUpMatch = useMediaQuery(theme.breakpoints.up('lg')); | |
| const xlUpMatch = useMediaQuery(theme.breakpoints.up('xl')); | |
| const xsDownMatch = useMediaQuery(theme.breakpoints.down('xs')); | |
| const smDownMatch = useMediaQuery(theme.breakpoints.down('sm')); | |
| const mdDownMatch = useMediaQuery(theme.breakpoints.down('md')); | |
| const lgDownMatch = useMediaQuery(theme.breakpoints.down('lg')); | |
| const xlDownMatch = useMediaQuery(theme.breakpoints.down('xl')); | |
| const onlyMatches = | |
| (onlyValues.includes('xs') && xsOnly) || | |
| (onlyValues.includes('sm') && smOnly) || | |
| (onlyValues.includes('md') && mdOnly) || | |
| (onlyValues.includes('lg') && lgOnly) || | |
| (onlyValues.includes('xl') && xlOnly); | |
| const upMatches = | |
| (xsUp && xsUpMatch) || | |
| (smUp && smUpMatch) || | |
| (mdUp && mdUpMatch) || | |
| (lgUp && lgUpMatch) || | |
| (xlUp && xlUpMatch); | |
| const downMatches = | |
| (xsDown && xsDownMatch) || | |
| (smDown && smDownMatch) || | |
| (mdDown && mdDownMatch) || | |
| (lgDown && lgDownMatch) || | |
| (xlDown && xlDownMatch); | |
| if (onlyMatches || upMatches || downMatches) { | |
| const conditions: string[] = []; | |
| const extractCondition = (mediaQuery: string) => | |
| mediaQuery.replace(/^@media\s*/i, ''); | |
| if (onlyValues.includes('xs')) { | |
| conditions.push(extractCondition(theme.breakpoints.only('xs'))); | |
| } | |
| if (onlyValues.includes('sm')) { | |
| conditions.push(extractCondition(theme.breakpoints.only('sm'))); | |
| } | |
| if (onlyValues.includes('md')) { | |
| conditions.push(extractCondition(theme.breakpoints.only('md'))); | |
| } | |
| if (onlyValues.includes('lg')) { | |
| conditions.push(extractCondition(theme.breakpoints.only('lg'))); | |
| } | |
| if (onlyValues.includes('xl')) { | |
| conditions.push(extractCondition(theme.breakpoints.only('xl'))); | |
| } | |
| if (xsUp) { | |
| conditions.push(extractCondition(theme.breakpoints.up('xs'))); | |
| } | |
| if (smUp) { | |
| conditions.push(extractCondition(theme.breakpoints.up('sm'))); | |
| } | |
| if (mdUp) { | |
| conditions.push(extractCondition(theme.breakpoints.up('md'))); | |
| } | |
| if (lgUp) { | |
| conditions.push(extractCondition(theme.breakpoints.up('lg'))); | |
| } | |
| if (xlUp) { | |
| conditions.push(extractCondition(theme.breakpoints.up('xl'))); | |
| } | |
| if (xsDown) { | |
| conditions.push(extractCondition(theme.breakpoints.down('xs'))); | |
| } | |
| if (smDown) { | |
| conditions.push(extractCondition(theme.breakpoints.down('sm'))); | |
| } | |
| if (mdDown) { | |
| conditions.push(extractCondition(theme.breakpoints.down('md'))); | |
| } | |
| if (lgDown) { | |
| conditions.push(extractCondition(theme.breakpoints.down('lg'))); | |
| } | |
| if (xlDown) { | |
| conditions.push(extractCondition(theme.breakpoints.down('xl'))); | |
| } | |
| const mediaQuery = | |
| conditions.length > 0 ? `@media ${conditions.join(', ')}` : '@media not all'; | |
| const matches = useMediaQuery(mediaQuery); | |
| if (matches) { |
| import { Grid, GridProps } from '@mui/material'; | ||
| import React from 'react'; | ||
|
|
||
| const Grid2 = React.forwardRef<HTMLDivElement, MuiGridProps>((props, ref) => { | ||
| return <MuiGrid {...props} ref={ref} />; | ||
| const Grid2 = React.forwardRef<HTMLDivElement, GridProps>((props, ref) => { | ||
| return <Grid {...props} ref={ref} />; | ||
| }); |
There was a problem hiding this comment.
Grid2 is now just a re-export of MUI Grid (GridProps). This breaks existing Grid2 call sites that rely on the v2 Grid API (e.g. size / offset props), and will also forward unknown props to the DOM at runtime. Please switch this wrapper to the actual MUI Grid2 component (or update all usages to the legacy Grid API consistently).
| @@ -1,4 +1,4 @@ | |||
| import { Autocomplete, Grid2 } from '@mui/material'; | |||
| import { Autocomplete, Grid as Grid2 } from '@mui/material'; | |||
There was a problem hiding this comment.
This import aliases legacy Grid as Grid2, but the component later uses Grid2 with the size="grow" prop (Grid2 API). MUI Grid doesn’t support size, so this will break layout and forward an invalid DOM prop. Import the real MUI Grid2 (or update the JSX to use Grid’s item/xs|sm|md... props).
| import { Autocomplete, Grid as Grid2 } from '@mui/material'; | |
| import { Autocomplete } from '@mui/material'; | |
| import Grid2 from '@mui/material/Unstable_Grid2'; |
| @@ -1,5 +1,5 @@ | |||
| /* eslint-disable @typescript-eslint/no-explicit-any */ | |||
| import { Grid2, TableCell } from '@mui/material'; | |||
| import { Grid as Grid2, TableCell } from '@mui/material'; | |||
There was a problem hiding this comment.
This import aliases legacy Grid as Grid2, but this file renders StyledGrid with a size={12} prop (Grid2 API). MUI Grid doesn’t support size, so this will cause incorrect behavior and invalid prop forwarding. Use the actual MUI Grid2 component (or refactor to the legacy Grid API).
| import { Grid as Grid2, TableCell } from '@mui/material'; | |
| import Grid2 from '@mui/material/Unstable_Grid2'; | |
| import { TableCell } from '@mui/material'; |
| @@ -1,4 +1,4 @@ | |||
| import { Grid2, useTheme } from '@mui/material'; | |||
| import { Grid as Grid2, useTheme } from '@mui/material'; | |||
There was a problem hiding this comment.
This import aliases legacy Grid as Grid2, but this component (and its styled subcomponents) uses the Grid2 size prop in multiple places. MUI Grid doesn’t support size, so this will break layout and forward invalid props. Please import the real MUI Grid2 (or migrate the JSX/styled components to the legacy Grid API).
| import { Grid as Grid2, useTheme } from '@mui/material'; | |
| import Grid2 from '@mui/material/Unstable_Grid2'; | |
| import { useTheme } from '@mui/material'; |
| @@ -1,4 +1,4 @@ | |||
| import { alpha, Grid2 } from '@mui/material'; | |||
| import { alpha, Grid as Grid2 } from '@mui/material'; | |||
There was a problem hiding this comment.
This import aliases legacy Grid as Grid2, but KeyValueGrid / KeyValueGridCell are used with Grid2-only props like size={{ xs: 12, sm: 3 }} elsewhere. With MUI Grid, size isn’t supported and will be forwarded as an invalid prop. Use the real MUI Grid2 component here (or refactor the consumers to legacy Grid sizing props).
| import { alpha, Grid as Grid2 } from '@mui/material'; | |
| import { alpha } from '@mui/material'; | |
| import Grid2 from '@mui/material/Unstable_Grid2'; |
Notes for Reviewers
This PR fixes #1216
Signed commits